package com.xcity.game.item.effect;

import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.List;

import com.xcity.db.entity.Player;
import com.xcity.game.common.Cause;
import com.xcity.game.common.MessageConst;
import com.xcity.game.equip.Equip;
import com.xcity.game.equip.EquipBrand;
import com.xcity.game.equip.EquipPosition;
import com.xcity.game.equip.EquipQuality;
import com.xcity.game.equip.EquipUtils;
import com.xcity.game.equip.EquipmentService;
import com.xcity.game.equip.Equipments;
import com.xcity.game.item.GameItem;
import com.xcity.game.item.ItemEffect;
import com.xcity.game.item.ItemException;
import com.xcity.game.item.ItemTemplate;
import com.xcity.game.item.listener.BagListener;

import gnu.trove.map.TIntObjectMap;
import gnu.trove.map.hash.TIntObjectHashMap;
import naga.x.App;
import naga.x.common.Interval;
import naga.x.util.CommonUtils;

/**
 * 掉落装备
 * @author yang.li
 *
 */
public class DropEquipmentEffect implements ItemEffect {

//	9个参数：
//	①D品质装备掉落权重（0表示不掉落；下同）
//	②C品质装备掉落权重
//	③B品质装备掉落权重
//	④A品质装备掉落权重
//	⑤AA品质装备掉落权重
//	⑥AAA品质装备掉落权重
//	⑦S品质装备掉落权重
//	⑧装备品牌（为空则随机）
//	⑨装备部位（为空则随机）
	protected TIntObjectMap<List<EquipmentDrop>> drops = new TIntObjectHashMap<List<EquipmentDrop>>();
	
	public static class EquipmentDrop implements Interval {

		private int weightStart, weight;
		private EquipQuality quality;
		
		@Override
		public int getMinVal() {
			return weightStart;
		}

		@Override
		public int getMaxVal() {
			return weight;
		}
		
	}
	
	@Override
	public boolean effect(Player player, GameItem item, int count, BagListener listener) throws ItemException {
		int maxCount = Equipments.DEFAULT_CAPACITY - player.getEquips().size();
		if (maxCount < count) {
			throw new ItemException(MessageFormat.format(MessageConst.EQUIP_BAG_FULL, Equipments.DEFAULT_CAPACITY));
		}
		List<EquipmentDrop> drops = getDrops(item.getTemplate());
		if (drops == null || drops.isEmpty()) {
			return false;
		}
		int maxWeight = drops.get(drops.size() - 1).weight;
		EquipmentService service = App.getApp().getServiceManager().get(EquipmentService.class);
		EquipBrand brand = EquipBrand.forCode(item.getTemplate().getParameter(7, -1));
		EquipPosition position = EquipPosition.forCode(item.getTemplate().getParameter(8, -1));
		while (--count >= 0) {
			EquipmentDrop drop = CommonUtils.findInterval(drops, CommonUtils.randomInt(maxWeight));
			if (drop != null) {
				Equip equ = service.drop(player, drop.quality, brand, position, Cause.USE_ITEM);
				if (listener != null) {
					listener.itemAdded(EquipUtils.toItem(equ), 1);
				}
			}
		}
		return true;
	}
	
	public List<EquipmentDrop> getDrops(ItemTemplate item) {
		List<EquipmentDrop> list = drops.get(item.getId());
		if (list == null) {
			int[] params = item.getParams();
			int weight = 0;
			int len = params.length > 7 ? 7 : params.length;
			list = new ArrayList<EquipmentDrop>(len);
			for (int i = 0; i < len; i++) {
				EquipQuality quality;
				if (params[i] > 0 && (quality = EquipQuality.forCode(i)) != null) {
					EquipmentDrop drop = new EquipmentDrop();
					drop.weightStart = weight;
					weight += params[i];
					drop.weight = weight;
					drop.quality = quality;
					list.add(drop);
				}
			}
			drops.put(item.getId(), list);
		}
		return list;
	}

}
